package com.ssy.lingxi.transaction.serviceimpl;

import cn.hutool.core.bean.BeanUtil;
import com.ssy.lingxi.common.model.dto.UserLoginCacheDTO;
import com.ssy.lingxi.common.response.PageData;
import com.ssy.lingxi.common.response.ResponseCode;
import com.ssy.lingxi.common.response.Wrapper;
import com.ssy.lingxi.transaction.api.common.OrderConstant;
import com.ssy.lingxi.transaction.api.dto.request.ProductQuotationDetailsRequest;
import com.ssy.lingxi.transaction.api.dto.request.ProductQuotationListRequest;
import com.ssy.lingxi.transaction.api.dto.response.ExternalInquiryListLogResponse;
import com.ssy.lingxi.transaction.api.dto.response.LogStateResponse;
import com.ssy.lingxi.transaction.api.dto.response.ProductQuotationDetailsResponse;
import com.ssy.lingxi.transaction.api.dto.response.ProductQuotationListResponse;
import com.ssy.lingxi.transaction.api.enums.InquiryExternalStatusEnum;
import com.ssy.lingxi.transaction.api.enums.QuoteInteriorStatusEnum;
import com.ssy.lingxi.transaction.entity.Quote;
import com.ssy.lingxi.transaction.entity.record.InquiryExternalRecord;
import com.ssy.lingxi.transaction.repository.InquiryExternalRecordRepository;
import com.ssy.lingxi.transaction.repository.QuoteRepository;
import com.ssy.lingxi.transaction.service.IPlatformQuoteService;
import com.ssy.lingxi.workflow.api.feign.ProcessFeign;
import com.ssy.lingxi.workflow.api.model.contant.ProcessEnum;
import com.ssy.lingxi.workflow.api.model.vo.request.ExternalProcessQueryVO;
import com.ssy.lingxi.workflow.api.model.vo.response.SimpleProcessDefVO;
import com.ssy.lingxi.workflow.api.model.vo.response.SimpleTaskVO;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.util.ObjectUtils;

import javax.annotation.Resource;
import javax.persistence.criteria.Order;
import javax.persistence.criteria.Predicate;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 平台后台-询价报价
 *
 * @author wrc
 * @date 2020/8/24
 */
@Service
public class PlatformQuoteServiceImpl implements IPlatformQuoteService {

    @Resource
    QuoteRepository quoteRepository;

    @Resource
    ProcessFeign processFeign;

    @Resource
    InquiryExternalRecordRepository inquiryExternalRecordRepository;

    /**
     * 平台后台-询价报价-报价单列表查询
     *
     * @author wrc
     * @date 2020/8/24
     */
    @Override
    public Wrapper<PageData<ProductQuotationListResponse>> productQuotationList(ProductQuotationListRequest request, UserLoginCacheDTO sysUser) {
        Pageable page = PageRequest.of(request.getCurrent(), request.getPageSize());
        Page<Quote> result = quoteRepository.findAll(getSpecification(request), page);
        List<ProductQuotationListResponse> countryAreaListResponseList = result.getContent().stream().map(quote -> {
            ProductQuotationListResponse productQuotationListResponse = BeanUtil.copyProperties(quote, ProductQuotationListResponse.class);
            productQuotationListResponse.setInteriorStateName(QuoteInteriorStatusEnum.getName(productQuotationListResponse.getInteriorState()));
            productQuotationListResponse.setExternalStateName(InquiryExternalStatusEnum.getName(productQuotationListResponse.getExternalState()));
            productQuotationListResponse.setOfferMemberId(quote.getCreateMemberId());
            productQuotationListResponse.setOfferMemberName(quote.getCreateMemberName());
            productQuotationListResponse.setOfferMemberRoleId(quote.getCreateRoleId());
            return productQuotationListResponse;
        }).collect(Collectors.toList());
        return Wrapper.success(new PageData<>(result.getTotalElements(), countryAreaListResponseList));
    }

    /**
     * 平台后台 询价报价-报价单详情
     *
     * @author wrc
     * @date 2020/8/24
     */
    @Override
    public Wrapper<ProductQuotationDetailsResponse> productQuotationDetails(ProductQuotationDetailsRequest request, UserLoginCacheDTO sysUser) {
        ProductQuotationDetailsResponse productQuotationDetailsResponse = new ProductQuotationDetailsResponse();
        Quote productQuotation = quoteRepository.findById(request.getId()).orElse(null);
        if (ObjectUtils.isEmpty(productQuotation)) {
            return Wrapper.fail(ResponseCode.PURCHASE_DATA_RECORDS_DON_T_EXIST);
        }
        BeanUtils.copyProperties(productQuotation, productQuotationDetailsResponse);
        getExternalLog(productQuotationDetailsResponse, productQuotation);
        productQuotationDetailsResponse.setExternalStateName(InquiryExternalStatusEnum.getName(productQuotationDetailsResponse.getExternalState()));
        return Wrapper.success(productQuotationDetailsResponse);
    }

    /**
     * 构建查询条件
     */
    private Specification<Quote> getSpecification(ProductQuotationListRequest request) {
        return (Specification<Quote>) (root, query, criteriaBuilder) -> {
            Predicate finalConditions = criteriaBuilder.conjunction();

            String details = request.getDetails();
            String inquiryListNo = request.getInquiryListNo();
            String quotationNo = request.getQuotationNo();
            String memberName = request.getMemberName();
            String offerMemberName = request.getOfferMemberName();
            Long startDocumentsTime = request.getStartDocumentsTime();
            Long endDocumentsTime = request.getEndDocumentsTime();
            Integer externalState = request.getExternalState();
            Integer interiorState = request.getInteriorState();

            //描述
            if(StringUtils.isNotEmpty(details)){
                Predicate predicate = criteriaBuilder.like(root.get("details"), "%" + details + "%");
                finalConditions = criteriaBuilder.and(finalConditions, predicate);
            }
            //询价单号
            if(StringUtils.isNotEmpty(inquiryListNo)){
                Predicate predicate = criteriaBuilder.like(root.get("inquiryListNo"), "%" + inquiryListNo + "%");
                finalConditions = criteriaBuilder.and(finalConditions, predicate);
            }
            //报价单号
            if(StringUtils.isNotEmpty(quotationNo)){
                Predicate predicate = criteriaBuilder.like(root.get("quotationNo"), "%" + quotationNo + "%");
                finalConditions = criteriaBuilder.and(finalConditions, predicate);
            }
            //询价会员名称
            if(StringUtils.isNotEmpty(memberName)){
                Predicate predicate = criteriaBuilder.like(root.get("memberName"), "%" + memberName + "%");
                finalConditions = criteriaBuilder.and(finalConditions, predicate);
            }
            //报价会员名称
            if(StringUtils.isNotEmpty(offerMemberName)){
                Predicate predicate = criteriaBuilder.like(root.get("createMemberName"), "%" + offerMemberName + "%");
                finalConditions = criteriaBuilder.and(finalConditions, predicate);
            }
            //开始单据时间
            if(startDocumentsTime != null && startDocumentsTime > 0){
                finalConditions = criteriaBuilder.and(finalConditions, criteriaBuilder.ge(root.get("voucherTime"), startDocumentsTime));
            }
            //结束单据时间
            if(endDocumentsTime != null && endDocumentsTime > 0){
                finalConditions = criteriaBuilder.and(finalConditions, criteriaBuilder.le(root.get("voucherTime"), endDocumentsTime));
            }
            //状态
            if (externalState != null && externalState > 0) {
                finalConditions = criteriaBuilder.and(finalConditions, criteriaBuilder.equal(root.get("externalState"), externalState));
            }
            if (interiorState != null && interiorState > 0) {
                finalConditions = criteriaBuilder.and(finalConditions, criteriaBuilder.equal(root.get("interiorState"), interiorState));
            }
            //排序
            Order createTimeOrder = criteriaBuilder.desc(root.get("id"));

            return query.orderBy(createTimeOrder).where(finalConditions).getRestriction();
        };
    }

//    /**
//     * sql拼接
//     *
//     * @author wrc
//     * @date 2020/7/31
//     */
//    private String sqlJointList(ProductQuotationListRequest request, String condition) {
//        String sbList = "SELECT  rf.create_member_name as offerMemberName,rf.member_name as memberName,rf.inquiry_list_id as inquiryListId,rf.quotation_no as quotationNo,rf.inquiry_list_no as inquiryListNo,rf.id as id,rf.details as details,rf.delivery_time as deliveryTime,rf.quotation_as_time as quotationAsTime,rf.voucher_time as voucherTime,rf.external_state as externalState,rf.interior_state as interiorState " +
//                "FROM trade_quote rf where 1=1 " +
//                condition +
//                " order by  rf.id desc " +
//                " limit " +
//                request.getPageSize() +
//                " OFFSET " +
//                request.getCurrent() * request.getPageSize();
//        return sbList;
//    }
//
//    /**
//     * sql拼接
//     *
//     * @author wrc
//     * @date 2020/7/31
//     */
//    private String sqlJointCount(String condition) {
//        String sbCount = "SELECT count(DISTINCT rf.id) FROM trade_quote rf  where 1=1 " +
//                condition;
//        return sbCount;
//    }
//
//    /**
//     * sql拼接
//     * queryType 查询类型：1.报价单查询 2. 待新增报价单查询 3.待审核报价单（一级） 4.待审核报价单（二级） 5.待提交报价单
//     *
//     * @author wrc
//     * @date 2020/7/31
//     */
//    private String sqlJointCondition(ProductQuotationListRequest request) {
//        StringBuilder sbCondition = new StringBuilder();
//        if (null != request && null != request.getDetails() && !request.getDetails().isEmpty()) {
//            sbCondition.append(" AND  rf.details like  '%");
//            sbCondition.append(request.getDetails());
//            sbCondition.append("%'");
//        }
//        if (null != request && null != request.getInquiryListNo() && !request.getInquiryListNo().isEmpty()) {
//            sbCondition.append(" AND  rf.inquiry_list_no LIKE '%");
//            sbCondition.append(request.getInquiryListNo());
//            sbCondition.append("%' ");
//        }
//        if (null != request && null != request.getQuotationNo() && !request.getQuotationNo().isEmpty()) {
//            sbCondition.append(" AND  rf.quotation_no like  '%");
//            sbCondition.append(request.getQuotationNo());
//            sbCondition.append("%' ");
//        }
//        if (null != request && null != request.getStartDocumentsTime() && null != request.getEndDocumentsTime()) {
//            sbCondition.append(" AND  rf.voucher_time BETWEEN ");
//            sbCondition.append(request.getStartDocumentsTime());
//            sbCondition.append(" and ");
//            sbCondition.append(request.getEndDocumentsTime());
//        }
//        if (null != request.getOfferMemberName() && !request.getOfferMemberName().isEmpty()) {
//            sbCondition.append(" AND  rf.create_member_name like  '%");
//            sbCondition.append(request.getOfferMemberName());
//            sbCondition.append("%' ");
//        }
//        if (null != request.getMemberName() && !request.getMemberName().isEmpty()) {
//            sbCondition.append(" AND   rf.member_name like  '%");
//            sbCondition.append(request.getMemberName());
//            sbCondition.append("%' ");
//        }
//
//        if (null != request.getInteriorState()) {
//            sbCondition.append(" and  rf.interior_state = ");
//            sbCondition.append(request.getInteriorState());
//        }
//        if (null != request.getExternalState()) {
//            sbCondition.append(" and   rf.external_state = ");
//            sbCondition.append(request.getExternalState());
//        }
//
//        return sbCondition.toString();
//    }

    /**
     * 获取报价单单外部操作流程
     */
    private void getExternalLog(ProductQuotationDetailsResponse productQuotationDetailsResponse, Quote productQuotation) {
        //获取外部流转记录
        List<InquiryExternalRecord> logs = inquiryExternalRecordRepository.findAllByInquiryListIdEquals(productQuotation.getInquiryListId());
        List<LogStateResponse> externalQuotationStateResponses = new ArrayList<>();
        ExternalProcessQueryVO taskStepVO = new ExternalProcessQueryVO();
        taskStepVO.setProcessKey(ProcessEnum.TRADE_INQUIRY_EXTERNAL.getProcessKey());
        taskStepVO.setRoleId(productQuotation.getMemberRoleId());
        Wrapper<SimpleProcessDefVO> listWrapper = processFeign.findSimpleExternalTaskDefinitions(taskStepVO);
        if (ResponseCode.SUCCESS.getCode() != listWrapper.getCode()) {
            return;
        }
        List<SimpleTaskVO> data = listWrapper.getData().getTasks();
        data.forEach(taskStepQueryVO -> {
            LogStateResponse externalRequisitionFormResponse = new LogStateResponse();
            externalRequisitionFormResponse.setState(taskStepQueryVO.getTaskStep());
            externalRequisitionFormResponse.setRoleName(taskStepQueryVO.getRoleName());
            externalRequisitionFormResponse.setOperationalProcess(taskStepQueryVO.getTaskName());
            if (CollectionUtils.isEmpty(logs)) {
                externalRequisitionFormResponse.setIsExecute(OrderConstant.State.STOP);
            } else {
                Integer state = logs.get(logs.size() - 1).getState();
                externalRequisitionFormResponse.setIsExecute(state >= taskStepQueryVO.getTaskStep() ? OrderConstant.State.START : OrderConstant.State.STOP);
            }
            externalQuotationStateResponses.add(externalRequisitionFormResponse);
        });
        if(!CollectionUtils.isEmpty(externalQuotationStateResponses)){
            externalQuotationStateResponses.get(0).setIsExecute(OrderConstant.State.START );
        }
        productQuotationDetailsResponse.setExternalQuotationStateResponses(externalQuotationStateResponses);
        if (CollectionUtils.isEmpty(logs)) {
            return;
        }
        List<ExternalInquiryListLogResponse> externalInquiryListLogResponses = logs.stream().map(temp -> {
            ExternalInquiryListLogResponse response = new ExternalInquiryListLogResponse();
            BeanUtils.copyProperties(temp, response);
            response.setStateName(InquiryExternalStatusEnum.getName(response.getState()));
            return response;
        }).collect(Collectors.toList());
        productQuotationDetailsResponse.setExternalRequisitionFormResponses(externalInquiryListLogResponses);
    }
}
